package com.atguigu.test.aop;

import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.core.annotation.Order;
import org.springframework.stereotype.Component;

/**
 * @author zp
 * @version 1.0
 * @description: TODO
 * @date 2022/9/7 18:43
 */
@Component //注入容器
@Aspect //开启代理
@Order(1) //当前一个类被多个类代理时 同事配置了相同的通知 可以配置这个属性保证执行顺序 越小执行越优先 （数值类型）
@Slf4j
public class CatProxy {
    /**
     * @description:  切入点方法 写一个后面的execution表达式可以重用
     * @author zp
     * @date: 2022/9/7 18:55
     */
    @Pointcut(value = "execution(* com.atguigu.test.aop.Cat.add(..))")
    public void eat(){

    }

    /**
     * @description:  前置通知
     * @author zp
     * @date: 2022/9/7 18:51
     */
    @Before(value="eat()")
    public void before(){
        log.info("CatProxy 执行了before通知");
    }
    /**
     * @description:  后置通知（也叫做最终通知 不管怎么样都会执行）
     * @author zp
     * @date: 2022/9/7 18:51
     */
    @After(value = "execution(* com.atguigu.test.aop.Cat.add(..))")
    public void after(){
        log.info("执行了after通知");
    }
    /**
     * @description:  返回通知（也被称为后置通知）
     * @author zp
     * @date: 2022/9/7 18:51
     */
    @AfterReturning(value = "execution(* com.atguigu.test.aop.Cat.add(..))")
    public void afterReturning(){
        log.info("执行了afterReturning通知");
    }
    /**
     * @description:  异常通知（出现异常的时候才会执行的方法）
     * @author zp
     * @date: 2022/9/7 18:51
     */
    @AfterThrowing(value = "execution(* com.atguigu.test.aop.Cat.add(..))")
    public void afterThrowing(){
        log.info("执行了afterThrowing通知");
    }
    /**
     * @description:  环绕通知
     * @author zp
     * @date: 2022/9/7 18:51
     */
    @Around(value = "execution(* com.atguigu.test.aop.Cat.add(..))")
    public void around(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
        log.info("执行了环绕around通知前");
        proceedingJoinPoint.proceed();
        log.info("执行了环绕around通知后");
    }
}
